"use strict";

import { tools, formatPath, npm } from "@p-test-cli/utils";
import path from "path";

const pathExists = require("path-exists").sync;
const fse = require("fs-extra");
const pkgDir = require("pkg-dir").sync;
const npminstall = require("npminstall");
class Package {
  targetPath;
  storePath;
  packageName;
  packageVersion;
  storeDir;
  cacheFilePathPrefix;
  constructor(options) {
    if (!options) {
      throw new Error("Package类的options参数不能为空！");
    }
    if (!tools.isObject(options)) {
      throw new Error("Package类的options参数必须为对象！");
    }
    //packake的路径
    this.targetPath = options.targetPath;
    //this.storePath = options.storePath;
    this.storeDir = options.storeDir;
    this.packageName = options.packageName;
    this.packageVersion = options.packageVersion;
    console.log(`packagename + ${this.packageName}`);
    this.cacheFilePathPrefix = `.store/${this.packageName.replace("/", "_")}`;
  }

  async prepare() {
    if (this.storeDir && !pathExists(this.storeDir)) {
      fse.mkdirpSync(this.storeDir);
    }
    if (this.packageVersion === "latest") {
      this.packageVersion = await npm.getNpmLatestVersion(this.packageName);
    }
  }
  get cacheFilePath() {
    return path.resolve(
      this.storeDir,
      `${this.cacheFilePathPrefix}@${this.packageVersion}/node_modules/${this.packageName}`
    );
  }

  getSpecificCacheFilePath(packageVersion) {
    return path.resolve(
      this.storeDir,
      `${this.cacheFilePathPrefix}@${packageVersion}/node_modules/${this.packageName}`
    );
  }
  async exists() {
    if (this.storeDir) {
      await this.prepare();
      return pathExists(this.cacheFilePath);
    } else {
      return pathExists(this.targetPath);
    }
  }

  async install() {
    await this.prepare();
    return npminstall({
      root: this.targetPath,
      storeDir: this.storeDir,
      registry: npm.getNpmRegistry(),
      pkgs: [{ name: this.packageName, version: this.packageVersion }],
    });
  }

  async update() {
    await this.prepare();
    const latestPackageVersion = await npm.getNpmLatestVersion(
      this.packageName
    );

    const latestFilePath = this.getSpecificCacheFilePath(latestPackageVersion);
    if (!pathExists(latestFilePath)) {
      await npminstall({
        root: this.targetPath,
        storeDir: this.storeDir,
        registry: npm.getNpmRegistry(),
        pkgs: [{ name: this.packageName, version: latestPackageVersion }],
      });
      this.packageVersion = latestPackageVersion;
    }
  }

  getRootFilePath() {
    function _getRootFile(targetPath) {
      const dir = pkgDir(targetPath);
      if (dir) {
        const pkgFile = require(path.resolve(dir, "package.json"));

        if (pkgFile && pkgFile.main) {
          return formatPath(path.resolve(dir, pkgFile.main));
        }
      }
      return null;
    }
    if (this.storeDir) {
      return _getRootFile(this.cacheFilePath);
    } else {
      return _getRootFile(this.targetPath);
    }
  }
}

export = { Package };
